package com.ds.home.proxy;

import com.alibaba.fastjson.annotation.JSONField;
import com.ds.command.CommandFactory;
import com.ds.common.JDSException;
import com.ds.context.JDSActionContext;
import com.ds.home.EIZNode;
import com.ds.home.client.CommandClient;
import com.ds.home.engine.AppEngine;
import com.ds.iot.*;
import com.ds.iot.enums.DeviceStatus;
import com.ds.iot.enums.ZNodeZType;

import java.io.Serializable;
import java.util.*;

public class ZNodeProxy implements ZNode, Serializable {
    private final String systemCode;
    @JSONField(serialize = false)

    private EIZNode znode;

    @JSONField(serialize = false)

    private Map<String, String> contextMap;


    @JSONField(serialize = false)

    public EIZNode getZnode() {
        return znode;
    }

    public void setZnode(EIZNode znode) {
        this.znode = znode;
    }

    public ZNodeProxy(EIZNode znode, String systemCode) {
        this.znode = znode;
        this.contextMap = JDSActionContext.getActionContext().getContext();
        this.systemCode = systemCode;

    }


    public Integer getChannel() {
        return znode.getChannel();
    }

    @JSONField(serialize = false)

    public List<ZNode> getChildNodeList() {
        List<ZNode> childNodes = new ArrayList<ZNode>();
        try {
            List<ZNode> ichildNodes = AppEngine.getEngine(systemCode).getAllChildNode(this.getZnodeid());
            for (ZNode znode : ichildNodes) {
                if (!znode.getStatus().equals(DeviceStatus.DELETE)) {
                    childNodes.add(znode);
                }
            }
        } catch (HomeException e) {
        }
        return childNodes;
    }

    //
    public String getCreateuiserid() {
        String createIdKey = "createId[" + this.getZnodeid() + "]";
        String createId = contextMap.get(createIdKey);
        if (createId == null) {

            createId = znode.getCreateuiserid();

            contextMap.put(createIdKey, createId);

        }

        return createId;
    }

    @JSONField(serialize = false)

    public Device getDevice() {
        Device device = null;
        try {
            device = AppEngine.getEngine(systemCode).getDeviceById(this.getDeviceid());
        } catch (HomeException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        return device;
    }

    public String getDeviceid() {
        return znode.getDeviceid();
    }

    public String getMacaddress() {
        return znode.getMacaddress();
    }

    public String getMasterkey() {
        return znode.getMasterkey();
    }

    public String getName() {
        return znode.getName();
    }

    public String getPanid() {
        return znode.getPanid();
    }

    @JSONField(serialize = false)

    public ZNode getParentNode() {
        ZNode znode = null;
        try {
            znode = AppEngine.getEngine(systemCode).getZNodeById(this.getParentid());
        } catch (HomeException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
            ;

        }
        return znode;
    }

    public String getParentid() {
        return znode.getParentid();
    }


    public String getProfilepath() {
        return znode.getProfilepath();
    }

    public Integer getSensortype() {
        return znode.getSensortype();
    }

    public DeviceStatus getStatus() {
        String statusKey = "status[" + this.getZnodeid() + "]";
        String status = contextMap.get(statusKey);
        if (status == null) {
            status = znode.getEndPoint().getDevice().getStates().toString();
//            if (znode.getEndPoint() != null && znode.getEndPoint().getDevice() != null && znode.getEndPoint().getDevice().getDevicetype() == 0) {
//                String gwIeee = znode.getEndPoint().getDevice().getSerialno();
//                CommandClient commandClient = null;
//                try {
//                    commandClient = CommandFactory.getInstance().getCommandClientByieee(gwIeee);
//                } catch (JDSException e) {
//                    e.printStackTrace();
//                }
//                if (commandClient == null) {
//                    return DeviceStatus.OFFLINE;
//                } else {
//                    return DeviceStatus.ONLINE;
//                }
//
//            } else {
//
//                if (status == null) {
//                    status = znode.getStatus().toString();
//
//                }
//
//            }

            contextMap.put(statusKey, status);

        }
        return DeviceStatus.fromCode(Integer.valueOf(status));
    }

    public String getZmoduleid() {
        return znode.getZmoduleid();
    }

    public String getZnodeid() {
        return znode.getZnodeid();
    }

    public ZNodeZType getZtype() {
        return ZNodeZType.fromType(znode.getZtype());
    }

    public void setChannel(Integer channel) {
        znode.setChannel(channel);

    }

    public void setCreateuiserid(String createuiserid) {
        String createIdKey = "createId[" + this.getZnodeid() + "]";
        znode.setCreateuiserid(createuiserid);
        contextMap.put(createIdKey, createuiserid);
    }

    public void setDeviceid(String deviceid) {
        znode.setDeviceid(deviceid);
    }

    public void setMacaddress(String macaddress) {
        znode.setMacaddress(macaddress);
    }

    public void setMasterkey(String masterkey) {
        znode.setMasterkey(masterkey);
    }

    public void setName(String name) {
        znode.setName(name);
    }

    public void setPanid(String panid) {
        znode.setPanid(panid);
    }

    public void setParentid(String parentid) {
        znode.setParentid(parentid);
    }


    public void setProfilepath(String profilepath) {
        znode.setProfilepath(profilepath);
    }

    public void setSensortype(Integer sensortype) {
        znode.setSensortype(sensortype);
    }

    public void setStatus(DeviceStatus status) {
        String statusKey = "status[" + this.getZnodeid() + "]";
        znode.setStatus(status.getCode());

        contextMap.put(statusKey, status.toString());
    }

    public void setZmoduleid(String zmoduleid) {
        znode.setZmoduleid(zmoduleid);
    }

    public void setZnodeid(String znodeid) {
        znode.setZnodeid(znodeid);
    }

    public void setZtype(ZNodeZType ztype) {
        znode.setZtype(ztype.getType());
    }

    @JSONField(serialize = false)

    public List<Alarm> getAlarmList() {
        List<Alarm> alarms = new ArrayList<Alarm>();

        try {
            alarms = AppEngine.getEngine(systemCode).getAlarmBySensorId(this.getZnodeid());
        } catch (HomeException e) {
        }
        return alarms;
    }

    @JSONField(serialize = false)

    public List<Scene> getSceneList() {
        List<Scene> scenes = new ArrayList<Scene>();
        try {
            scenes = AppEngine.getEngine(systemCode).getSceneBySensorId(this.getZnodeid());
        } catch (HomeException e) {
        }
        return scenes;
    }

    public boolean equals(Object object) {
        if (this == object) {
            return true;
        }

        if (object != null && object instanceof ZNode) {
            return this.getZnodeid().equals(((ZNode) object).getZnodeid());
        } else {
            return false;
        }
    }

    public Scene getDefaultScene() {
        Scene defaultScene = null;
        for (Scene scene : getSceneList()) {
            if (scene != null && scene.getStatus() == HomeConstants.ZNNODE_ALARM_STATUS_DEFAULT) {
                scene = defaultScene;
                break;
            }
        }
        return defaultScene;
    }


    public String getEndPointid() {
        return znode.getEndPointid();
    }

    public void setEndPointid(String endpointid) {
        znode.setEndPointid(endpointid);
    }

    @JSONField(serialize = false)

    public DeviceEndPoint getEndPoint() {
        DeviceEndPoint endPoint = null;
        try {
            if (this.getEndPointid() == null) {
                Device device = AppEngine.getEngine(systemCode).getDeviceById(this.getDeviceid());
                String serialno = device.getSerialno();
                try {
                    endPoint = AppEngine.getEngine(systemCode).getEndPointSerialno(serialno);
                } catch (HomeException e) {
                    endPoint = AppEngine.getEngine(systemCode).registerEndPoint(device.getSerialno(), device.getSerialno(), null, device.getSensortype().getType(), device.getSensortype().getName());
                }

                this.znode.setEndPointid(endPoint.getEndPointId());
                AppEngine.getEngine(systemCode).updateZNode(AppEngine.getEngine(systemCode).getZNodeById(znode.getZnodeid()), true);
            } else {
                endPoint = AppEngine.getEngine(systemCode).getEndPoint(this.getEndPointid());
            }
        } catch (HomeException e) {
            e.printStackTrace();
        }

        return endPoint;
    }


    public Set<String> getChildNodeIdList() {
        List<ZNode> nodes = this.getChildNodeList();
        Set<String> nodeIds = new LinkedHashSet<String>();
        for (ZNode znode : nodes) {
            if (znode.getEndPoint() != null && znode.getEndPoint().getDevice() != null && !znode.getEndPoint().getDevice().getStates().equals(DeviceStatus.DELETE)) {
                nodeIds.add(znode.getZnodeid());
            }

        }
        return nodeIds;
    }
}
